package com.alinesno.cloud.gateway.core.dispather;

import java.net.InetSocketAddress;

import org.apache.mina.core.service.IoHandlerAdapter;
import org.apache.mina.core.session.IdleStatus;
import org.apache.mina.core.session.IoSession;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.alinesno.cloud.gateway.core.context.ApplicationContextProvider;
import com.alinesno.cloud.gateway.core.dispather.mina.MinaSocketProxyFactory;
import com.alinesno.cloud.gateway.core.dispather.mina.bean.BusinessServerBean;
import com.alinesno.cloud.gateway.core.dispather.mina.bean.MessageBean;
import com.alinesno.cloud.gateway.core.dispather.mina.bean.MessageBuilder;

/**
 * 服务异常信息
 * 
 * @author WeiXiaoJin
 * @since 2020年1月31日 下午19:45:08
 */
public class SocketDispather extends IoHandlerAdapter implements BaseDispather {

	private static final Logger log = LoggerFactory.getLogger(SocketDispather.class);

	private BusinessServerBean server;

	public SocketDispather(BusinessServerBean server) {
		this.server = server;
	}

	@Override
	public void sessionCreated(IoSession session) throws Exception {
		String clientIP = ((InetSocketAddress)session.getRemoteAddress()).getAddress().getHostAddress();
	    session.setAttribute("KEY_SESSION_CLIENT_IP", clientIP);
	    log.debug("sessionCreated, client IP: " + clientIP);
	}

	@Override
	public void messageReceived(IoSession session, Object message) throws Exception {
		log.debug("message = {}", message);

		Object factoryObj = ApplicationContextProvider.getBean("MINA_SOCKET_PROXY_" + server.getBusinessCode());

		if (factoryObj != null) {
			MinaSocketProxyFactory factory = (MinaSocketProxyFactory) factoryObj;
			MessageBean response = factory.handle(server, session, (MessageBean) message);

			session.write(response);
		} else {
			session.write(MessageBuilder.notService());
		}

		session.closeOnFlush();
	}

	@Override
	public void sessionOpened(IoSession session) throws Exception {
		super.sessionOpened(session);
	}

	@Override
	public void sessionClosed(IoSession session) throws Exception {
		super.sessionClosed(session);
	}

	@Override
	public void sessionIdle(IoSession session, IdleStatus status) throws Exception {

		if (status == IdleStatus.BOTH_IDLE) {
			session.write(MessageBuilder.outime());
			session.closeOnFlush();
		}

	}

	@Override
	public void exceptionCaught(IoSession session, Throwable cause) throws Exception {
		if(server.isHasHystrix()) {
			session.write(MessageBuilder.error(server.getHystrixContent())) ; 
		}else {
			session.write(MessageBuilder.error(null));
		}
		session.closeOnFlush();
	}

	@Override
	public void messageSent(IoSession session, Object message) throws Exception {
		super.messageSent(session, message);
	}

}
